package com.scut.fy.admin.controller;

import cn.dev33.satoken.stp.StpUtil;
import com.scut.fy.admin.model.vo.LoginVo;
import com.scut.fy.admin.model.vo.UserVo;
import com.scut.fy.admin.service.ImageCodeService;
import com.scut.fy.admin.service.UserService;
import com.scut.fy.common.core.constant.FyConstant;
import com.scut.fy.common.core.util.Assert;
import com.scut.fy.common.core.util.BeanUtils;
import com.scut.fy.common.web.model.HttpResult;
import com.scut.fy.common.web.util.UserAgentUtil;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.web.bind.annotation.*;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.util.HashMap;
import java.util.Map;

/**
 * 登录、登出，注册接口
 *
 * @author JY
 * @version 1.0
 * @date 2021/9/15
 */
@RestController
@RequestMapping("/acc")
public class AdminLoginController {

    private static Logger log = LoggerFactory.getLogger(AdminLoginController.class);
    @Resource
    private RedisTemplate redisTemplate;
    @Autowired
    private UserService userService;
    @Autowired
    private ImageCodeService imageCodeService;

    @PostMapping("/registry")
    public HttpResult<Boolean> registry(@RequestBody UserVo userVo) {
        HttpResult<Boolean> httpResult = new HttpResult<>();
        log.info("输入的用户信息userVo={}", userVo);
        try {
            long result = userService.insertUser(userVo);
            log.info("userVo={}注册用户成功", userVo);
            httpResult.setData(true);
        } catch (Exception e) {
            log.error("userVo={}注册用户失败", userVo);
            httpResult.setData(false);
            e.printStackTrace();
        } finally {
            return httpResult;
        }
    }

    @PostMapping("/dologin")
    public HttpResult<Map> login(@RequestBody LoginVo loginVo,
                                 HttpServletRequest request, HttpServletResponse response) {

        final HttpResult<Map> httpResult = new HttpResult<>();
        try {
            log.info("开始账号密码登录， loginVo={}", BeanUtils.beanToJson(loginVo));
            String userName = loginVo.getUserName();
            String pwd = loginVo.getPwd();
            String imageCode = loginVo.getImageCode();
            String randomStr = loginVo.getRandomStr();
            Assert.isBlank(userName, "用户名不能为空");
            Assert.isBlank(pwd, "密码不能为空");
            Assert.isBlank(imageCode, "验证码不能为空");
            Assert.isBlank(randomStr, "验证码异常");
            // 判断验证码的正确性
            HttpResult<Boolean> imageHttpResult = imageCodeService.checkImageCode(randomStr, imageCode);
            if (imageHttpResult.getData().equals(true)) {
                // 验证完了及时删除验证码
                log.info("验证码正确");
                redisTemplate.delete(FyConstant.DEFAULT_CODE_KEY + randomStr);
                // 校验账号密码的正确性
                UserVo userVo = userService.checkUserPwd(userName, pwd);
                if (null != userVo) {

                    Long userId = userVo.getUserId();
                    // 识别设备类型
                    String deviceType = UserAgentUtil.getDeviceType(request);
                    // 登录，指定设备标识登录，用于“同端互斥登录”
                    StpUtil.login(userId, deviceType);
                    if (StpUtil.isLogin()) {
                        // 把申请token返回前端
                        Map<String, String> map = new HashMap<>(2);
                        map.put(StpUtil.getTokenInfo().getTokenName(),StpUtil.getTokenInfo().getTokenValue());
                        httpResult.setData(map);
                        log.info("账号密码登录成功， SaTokenInfo={}", StpUtil.getTokenInfo());
                    }
                } else {
                    httpResult.setCode(HttpResult.BAD_REQUEST);
                    httpResult.setMsg("用户名或者密码错误");
                    httpResult.setData(null);
                    StpUtil.logout();
                }
            } else {
                log.info("验证码错误");
                httpResult.setMsg(imageHttpResult.getMsg());
                httpResult.setCode(imageHttpResult.getCode());
                httpResult.setData(null);
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return httpResult;
    }

    @PostMapping("/logout")
    public void logout(@RequestParam long userId, HttpServletRequest request) {
        // TODO
        final HttpResult<Boolean> httpResult = new HttpResult<>();
        // 识别设备类型
        String deviceType = UserAgentUtil.getDeviceType(request);
        // 会话注销登录（踢人下线）
        StpUtil.logoutByLoginId(userId, deviceType);
        StpUtil.checkLogin();
    }
}
